﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ComponentModel;
using System.Collections.ObjectModel;
using System.Xml.Serialization;
using System.Windows.Forms;
using System.Threading;

namespace BDSim
{
    public class MasterStation : StationBase
    {
        public MasterStation()
        {
            DataProvider.Parent = this;
            DataProvider.DefineCommand();
            Menu.ItemsSource = _DataProvider.MenuCommandList;
        }

        #region 字段

        /// <summary>
        /// 导航电文拟合类 
        /// </summary>
        private NavMsgFit _CNavMsgFit = new NavMsgFit();

        /// <summary>
        /// 主控站是否进行星历拟合
        /// </summary>
        private bool _IsNavFit = true;
       
        [XmlIgnore]
        public Dictionary<string, List<Ephemeris_16>> SatEph16Dic = new Dictionary<string, List<Ephemeris_16>>(); /// key（string）代表卫星名称，value代表当前卫星所有星历                                                                                                                  /// 
        [XmlIgnore]
        public Dictionary<EConstellationType, Dictionary<string, List<Ephemeris_16>>> SatEph16Dic_ConType;//分系统存储的不同星座的星历数据

        [XmlIgnore]
        public Dictionary<string, List<GlonassEph>> GloSatEphDic = new Dictionary<string, List<GlonassEph>>(); /// key（string）代表卫星名称，value代表当前卫星所有星历
        [XmlIgnore]                                                                                                       /// 
        public Dictionary<EConstellationType, Dictionary<string, List<GlonassEph>>> GloSatEphDic_ConType;//分系统存储的不同星座的星历数据

        [XmlIgnore]
        public Dictionary<string, List<ClkErrFitMsg>> ClockErrDic = new Dictionary<string, List<ClkErrFitMsg>>();  /// key（string）代表卫星名称，value代表当前卫星所有钟差值
        [XmlIgnore]                                                                                                          
        public Dictionary<EConstellationType,Dictionary<string, List<ClkErrFitMsg>>> ClockErrDic_ConType;//分系统存储的不同星座的星历数据

        [XmlIgnore]
        public List<IonoFit_OutputMsg> IonoFitOutputMsgList = new List<IonoFit_OutputMsg>();

        #endregion

        #region 属性

        /// <summary>
        /// 主控站是否进行星历拟合
        /// </summary>
        [XmlAttribute, Category("控制开关"), DescriptionAttribute("是否拟合导航电文")]
        public bool IsNavFit
        {
            get { return _IsNavFit; }
            set { _IsNavFit = value; NotifyPropertyChanged("IsNavFit"); }
        }

        /// <summary>
        /// 导航电文拟合类
        /// </summary>
        [XmlIgnore, Browsable(false)]
        public NavMsgFit CNavMsgFit
        {
            get { return _CNavMsgFit; }
            set { _CNavMsgFit = value; }
        }

        MasterStationDataProvider _DataProvider = new MasterStationDataProvider();

        [XmlIgnore, Browsable(false)]
        public MasterStationDataProvider DataProvider
        {
            get { return _DataProvider; }
            set { _DataProvider = value; }
        }

        int EphFitFlag = 0;//
        #endregion


        #region 初始化
        public override void Init()
        {
            //参数初始化      
            SatEph16Dic_ConType = new Dictionary<EConstellationType, Dictionary<string, List<Ephemeris_16>>>();
            GloSatEphDic_ConType = new Dictionary<EConstellationType, Dictionary<string, List<GlonassEph>>>();
            ClockErrDic_ConType = new Dictionary<EConstellationType, Dictionary<string, List<ClkErrFitMsg>>>();
            EphFitFlag = 0;//
            _CNavMsgFit.Parent = this;
            bool IsFitEphemerisFlag = (Parent.Parent.Parent.Parent as Scenario).IsFitEphemeris;

            if (IsFitEphemerisFlag == true && _IsNavFit == true)
            {
                NavMsgFitCal();
            }

            ClkErrCal();

            //初始化完成反馈任务执行量
            DlgAddCompleteMission();
        }
        #endregion

        #region 单步运行
        public override void StepRun()
        {

        }
        #endregion


        #region 功能一：导航电文参数拟合实现

        public void NavMsgFitCal()
        {
            ObservableCollection<Satellite> satsList =new ObservableCollection<Satellite> ();            
            EConstellationType contype = new EConstellationType();

            for (int i = 0; i < (Parent.Parent.Parent.Parent.SegmentColletion[0] as SpaceSegment).ConstellationList.Count(); i++)
            {
                contype=(Parent.Parent.Parent.Parent.SegmentColletion[0] as SpaceSegment).ConstellationList[i].ConstellationFeature.ConstellationType;

                if (contype == this.Parent.Parent.Type)
                {
                    satsList=(Parent.Parent.Parent.Parent.SegmentColletion[0] as SpaceSegment).ConstellationList[i].SatelliteCollection;

                    SatEph16Dic.Clear();
                    ClockErrDic.Clear();

                    CNavMsgFit.Msg_NavFit(satsList, contype);
                    CNavMsgFit.Msg_ClkFit(satsList);
                    CNavMsgFit.Msg_IonFit();
                    EphFitFlag = 1;

                    switch (contype)
                    {
                        //抽取星历16参
                        case EConstellationType.BD:
                        case EConstellationType.GALILEO:
                        case EConstellationType.GPS:
                            SatEph16Dic_ConType.Add(contype,SatEph16Dic);
                            ClockErrDic_ConType.Add(contype,ClockErrDic);
                            break;
                        case EConstellationType.GLONASS:
                            GloSatEphDic_ConType.Add(contype, GloSatEphDic);
                            ClockErrDic_ConType.Add(contype, ClockErrDic);
                            break;
                    }
                    break;
                }
            }

            if (0 == EphFitFlag)
            {
                MessageBox.Show("请添加与空间段中星座类型匹配的地面段，否则用户将不能定位！");
                Thread thd = Thread.CurrentThread;
                BDSimObject.GlobalStatus = ESimStatus.UnInited;
                this.Parent.Parent.Parent.Parent.Status = ESimStatus.UnInited;
                thd.Abort();
            }

        }

        #endregion

    }
}
